﻿using System;
using System.Linq;
using System.Collections.Generic;
using System.Text;
using FBEntities.FBObjects.User;
using System.Drawing;
using System.Windows.Forms;

namespace XFControls.XFPanels.XFPanelItems
{
    class XFItemProfileInfo : IXFItem
    {
        private FBPerson _user;
        private int _height;
        private int _indent = 15;
        private int _categoryHeight = 30;
        private int _singleLineText = 30;
        private SizeF _mesTitle;
        public XFItemStyle Style { get; set; }
        public XFItemType ItemType { get; set; }
        public FBPerson User
        {
            get
            {
                return _user;
            }
            set
            {
                _user = value;
                _user.Updated += (o, e) =>
                {
                    ResetHeight();

                    if (Buffer != null)
                        Buffer.Dispose();
                    Buffer = null;

                    if (Parent.InvokeRequired && !Parent.IsDisposed)
                        Parent.Invoke(new Action(() => { Parent.Invalidate(); }));
                };
            }
        }

        public XFItemProfileInfo()
        {
            _height = -1;
            _mesTitle = new SizeF(-1, -1);

            Style = new XFItemStyle()
            {
                TextFont = new Font(FontFamily.GenericSansSerif, 9, FontStyle.Regular),
                TextColor = Color.DarkSlateGray,
                Padding = 10
            };

            ItemType = XFItemType.Display;
        }

        #region IXFItem Members

        public XFPanelBase Parent { get; set; }

        public XFItemState State { get; set; }

        public int GetHeight()
        {
            if (_height > 0)
                return _height;
            int y = 0;

            int width = Screen.PrimaryScreen.WorkingArea.Width;
            int curY = Style.PaddingTop + y;

            curY = getCategoryHeight(curY);

            curY = getLineTextHeight(curY);
            curY = getLineTextHeight(curY);
            curY = getLineTextHeight(curY);
            curY = getLineTextHeight(curY);
            curY = getLineTextHeight(curY);
            curY = getLineTextHeight(curY);

            curY = getCategoryHeight(curY);

            curY = getParagraphTextHeight(width, User.Activities.ToString(), "Activities", curY);
            curY = getParagraphTextHeight(width, User.Interests.ToString(), "Interests", curY);
            curY = getParagraphTextHeight(width, User.Music.ToString(), "Music", curY);
            curY = getParagraphTextHeight(width, User.Television.ToString(), "TV", curY);
            curY = getParagraphTextHeight(width, User.Movies.ToString(), "Movies", curY);
            curY = getParagraphTextHeight(width, User.Books.ToString(), "Books", curY);
            curY = getParagraphTextHeight(width, User.quotes, "Quotes", curY);
            curY = getParagraphTextHeight(width, User.bio, "Bio", curY);

            _height = curY;

            return _height;
        }

        public void ResetHeight()
        {
            _height = -1;
        }

        public void ItemPaint(System.Drawing.Graphics gf, int x, int y)
        {
            int width = Screen.PrimaryScreen.WorkingArea.Width;
            int xLocal = 0;


            int curY = 0;
            Pen pCat = new Pen(Color.MidnightBlue);
            SolidBrush bCat = new SolidBrush(Color.LightSteelBlue);
            Font fCat = new Font(FontFamily.GenericSansSerif, 9, FontStyle.Regular);
            SolidBrush bText = new SolidBrush(Color.Black);

            curY = drawCategory(gf, width, "Basic Info", pCat, bCat, bText, fCat, xLocal, curY);

            curY = drawLineText(gf, width, "Profile:  " + User.link, bText, curY);
            curY = drawLineText(gf, width, "Email:  " + User.email, bText, curY);
            curY = drawLineText(gf, width, "Sex:  " + User.gender, bText, curY);
            curY = drawLineText(gf, width, "Birthday:  " + (User.birthday.HasValue ? User.birthday.Value.ToString() : ""), bText, curY);

            if (User.location != null)
                curY = drawLineText(gf, width, "Hometown:  " + User.location.name, bText, curY);
            else
                curY = drawLineText(gf, width, "Hometown:  N/A", bText, curY);
            curY = drawLineText(gf, width, "Relationship:  " + User.relationship_status, bText, curY);

            curY = drawCategory(gf, width, "Likes and Interests", pCat, bCat, bText, fCat, xLocal, curY);

            //  The category w/ the largest title must go first
            curY = drawParagraphText(gf, width, User.Activities.ToString(), "Activities", bText, curY);
            curY = drawParagraphText(gf, width, User.Interests.ToString(), "Interests", bText, curY);
            curY = drawParagraphText(gf, width, User.Music.ToString(), "Music", bText, curY);
            curY = drawParagraphText(gf, width, User.Television.ToString(), "TV", bText, curY);
            curY = drawParagraphText(gf, width, User.Movies.ToString(), "Movies", bText, curY);
            curY = drawParagraphText(gf, width, User.Books.ToString(), "Books", bText, curY);
            curY = drawParagraphText(gf, width, User.quotes, "Quotes", bText, curY);
            curY = drawParagraphText(gf, width, User.bio, "Bio", bText, curY);

            pCat.Dispose();
            bCat.Dispose();
            fCat.Dispose();
            bText.Dispose();
            gf.Dispose();
        }

        private int drawLineText(Graphics g, int width, string text, SolidBrush bText, int curY)
        {
            g.DrawString(XFControlUtils.EllipsisWord(width - (_indent * 2), text, Style.TextFont), Style.TextFont, bText, _indent, curY);
            return curY + _singleLineText;
        }

        private int getLineTextHeight(int curY)
        {
            return curY + _singleLineText;
        }

        private int drawParagraphText(Graphics g, int width, string text, string title, SolidBrush bText, int curY)
        {
            int ret = 0;
            title = title + ":  ";

            if (_mesTitle.Width < 0)
                _mesTitle = g.MeasureString(title, Style.TextFont);

            int titleWidth = (int)_mesTitle.Width;
            string fText = XFControlUtils.GetSizedString(width - (_indent * 2) - titleWidth, text, Style.TextFont);
            var mesText = g.MeasureString(fText, Style.TextFont);

            if ((ret = (int)mesText.Height + curY + Style.PaddingTop) < 0)
                return ret;

            g.DrawString(title, Style.TextFont, bText, _indent, curY);
            g.DrawString(fText, Style.TextFont, bText, _indent + titleWidth, curY);

            if (string.IsNullOrEmpty(text))
                return curY + _singleLineText;

            return ret;
        }

        private int getParagraphTextHeight(int width, string text, string title, int curY)
        {
            if (string.IsNullOrEmpty(text))
                return curY + _singleLineText;

            using (Graphics g = Graphics.FromImage(new Bitmap(100, 100)))
            {
                title = title + ":  ";

                if (_mesTitle.Width < 0)
                    _mesTitle = g.MeasureString(title, Style.TextFont);
            }
            
            int titleWidth = (int)_mesTitle.Width;
            string fText = XFControlUtils.GetSizedString(width - (_indent * 2) - titleWidth, text, Style.TextFont);
        
            using (Graphics g = Graphics.FromImage(new Bitmap(100, 100)))
            {

                int ret = curY + (int)g.MeasureString(fText, Style.TextFont).Height + Style.PaddingTop;
                return ret;
            }
        }

        private int drawCategory(Graphics g, int width, string title, Pen pCat, SolidBrush bCat, SolidBrush bText, Font fCat, int x, int curY)
        {
            int ret = curY + _categoryHeight + Style.PaddingTop;

            curY += Style.PaddingTop;
            g.FillRectangle(bCat, x, curY, width, _categoryHeight);
            g.DrawLine(pCat, x, curY, width, curY);

            g.DrawString(title, fCat, bText, x + Style.PaddingLeft, curY + 3);

            return ret;
        }

        private int getCategoryHeight(int curY)
        {
            return curY + _categoryHeight + (Style.PaddingLeft + Style.PaddingRight);
        }

        public XFItemClickResult GetClickResult()
        {
            return XFItemClickResult.Nothing;
        }

        #endregion

        #region IXFItem Members


        public Bitmap Buffer { get; set; }

        #endregion

        #region IDisposable Members

        public void Dispose()
        {
            if (Buffer != null)
                Buffer.Dispose();

            Buffer = null;
            if (Style != null)
                Style.Dispose();

            Style = null;
        }

        #endregion
    }
}
